home *** CD-ROM | disk | FTP | other *** search
/ BCI NET / BCI NET Dec 94.iso / archives / applications / databases / fbase106.lha / FBase / FBaseSrc.lha / Data.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-06-10  |  14.4 KB  |  597 lines

  1. /* $Revision Header *** Header built automatically - do not edit! ***********
  2.  *
  3.  *    (C) Copyright 1993 by Amit Fridman
  4.  *
  5.  *    Name .....: Data.c
  6.  *    Created ..: Tuesday 14-Dec-93 11:40:39
  7.  *    Revision .: 5
  8.  *
  9.  *    Date        Author                 Comment
  10.  *    =========   ====================   ====================
  11.  *    13-May-94   Amit Fridman           v1.05 Preliminary release
  12.  *    15-Apr-94   Amit Fridman           v1.04 Beta version complete
  13.  *    24-Mar-94   Amit Fridman           v1.03 Added Keys
  14.  *    24-Feb-94   Amit Fridman           v1.02
  15.  *    07-Jan-94   Amit Fridman           v1.01
  16.  *    14-Dec-93   Amit Fridman           Created this file!
  17.  *
  18.  * $Revision Header ********************************************************/
  19. #define REVISION    5
  20.  
  21. /* Floppy Base data handling routines */
  22.  
  23. #include "FBase.h"
  24. #include "Protos.h"
  25.  
  26. static BOOL    _ReadFloppy(struct List *RList,RECORD *Record,UWORD *Depth);
  27. static void    _DeleteBelow(RECORD *Record);
  28. static RECORD *_DupFloppy(struct List *RList,RECORD *Src,RECORD *Parent);
  29.  
  30. extern char *CY_Labels[];
  31.  
  32. struct List  FloppyList;
  33. STRPTR       KeyList[MAXKEYS];
  34. STRPTR       KeyListCopy[MAXKEYS];
  35.  
  36. static ULONG RecID;
  37. static int   KeyScan;
  38.  
  39. void myStartup()
  40. {
  41.    NewList(&FloppyList);
  42.    InitDiskNames();
  43.    SetSaveName();
  44.    ResetKeys();
  45. }
  46.  
  47. void myCleanup()
  48. {
  49.    int i;
  50.  
  51.    FreeKeys();
  52.    for (i=0; i<32; i++)
  53.       if (CY_Labels[i])
  54.          FreeMem(CY_Labels[i],strlen(CY_Labels[i])+1);
  55.    FreeAllFloppies(&FloppyList);
  56. }
  57.  
  58. BOOL ReadDirectory(char *BaseName,struct List *RList,RECORD *Parent,RECORD **Top,UWORD Depth)
  59. {
  60.    RECORD               *TopRecord = NULL;
  61.    RECORD               *Record;
  62.    STRPTR                String;
  63.    struct FileInfoBlock *fib;
  64.    BPTR                  lock;
  65.    BOOL                  error;
  66.  
  67.    fib=(struct FileInfoBlock *)AllocDosObject(DOS_FIB,NULL);
  68.    lock=Lock((STRPTR)BaseName,ACCESS_READ);
  69.    if (!lock) return(NULL);
  70.    if (Examine(lock,fib)==0) return(FALSE);
  71.    if (fib->fib_EntryType<0) return(FALSE);
  72.    error=FALSE;
  73.    while (!error) {
  74.       error=(ExNext(lock,fib)==0);
  75.       if (!error) {
  76.          Record=AllocMem(sizeof(RECORD),MEMF_CLEAR);
  77.          if (!Record)
  78.             return(FALSE);
  79.          Record->Parent=Parent;
  80.          Record->Size=fib->fib_Size;
  81.          Record->Depth=Depth;
  82.          if (fib->fib_EntryType>0)
  83.             Record->Flags|=RECORD_DIRECTORY;
  84.          String=AllocMem(strlen(fib->fib_FileName)+1,MEMF_CLEAR);
  85.          if (!String) return(FALSE);
  86.          strcpy(String,fib->fib_FileName);
  87.          Record->FName=String;
  88.          if (strlen(fib->fib_Comment)>0) {
  89.             String=AllocMem(strlen(fib->fib_Comment)+1,MEMF_CLEAR);
  90.             if (!String) return(FALSE);
  91.             strcpy(String,fib->fib_Comment);
  92.             Record->FRem=String;
  93.          }
  94.          Record->Unique=RecID++;
  95.          Record->Keys=0L;
  96.          if (AddRecordInPlace(RList,(struct Node *)Record,(struct Node *)Parent))
  97.             TopRecord=Record;
  98.       }
  99.    }
  100.    UnLock(lock);
  101.    FreeDosObject(DOS_FIB,(APTR)fib);
  102.    *Top=TopRecord;
  103.    return(TRUE);
  104. }
  105.  
  106. BOOL ReadFloppy(char *FloppyName,FLOPPY **pFloppy)
  107. {
  108.    FLOPPY               *Floppy;
  109.    RECORD               *Record;
  110.    struct FileInfoBlock *fib;
  111.    BPTR                  lock;
  112.    UWORD                 Depth;
  113.  
  114.    fib=(struct FileInfoBlock *)AllocDosObject(DOS_FIB,NULL);
  115.    lock=Lock((STRPTR)FloppyName,ACCESS_READ);
  116.    if (!lock) return(FALSE);
  117.    if (Examine(lock,fib)==0) return(FALSE);
  118.    UnLock(lock);
  119.    Floppy=AllocMem(sizeof(FLOPPY),MEMF_CLEAR);
  120.    if (!Floppy) return(FALSE);
  121.    NewList(&Floppy->Records);
  122.    Record=AllocMem(sizeof(RECORD),MEMF_CLEAR);
  123.    if (!Record) {
  124.       FreeMem(Floppy,sizeof(FLOPPY));
  125.       return(FALSE);
  126.    }
  127.    Record->FName=AllocMem(strlen(fib->fib_FileName)+1,MEMF_CLEAR);
  128.    if (!Record->FName) {
  129.       FreeRecord(Record,FALSE);
  130.       return(FALSE);
  131.    }
  132.    strcpy((char *)Record->FName,fib->fib_FileName);
  133.    Record->Flags=RECORD_DIRECTORY|RECORD_ROOT;
  134.    RecID=1;
  135.    Record->Unique=RecID++;
  136.    Record->Keys=0L;
  137.    Floppy->HeadRecord=Record;
  138.    AddTail(&Floppy->Records,(struct Node *)Record);
  139.    FreeDosObject(DOS_FIB,(APTR)fib);
  140.    Depth=0;
  141.    if (!_ReadFloppy(&Floppy->Records,Record,&Depth)) {
  142.       FreeFloppy(Floppy,FALSE);
  143.       return(FALSE);
  144.    }
  145.    *pFloppy=Floppy;
  146.    return(TRUE);
  147. }
  148.  
  149. static BOOL _ReadFloppy(struct List *RList,RECORD *Record,UWORD *Depth)
  150. {
  151.    RECORD *Sub;
  152.    char    BFName[108];
  153.  
  154.    while (Record) {
  155.       if (Record->Flags & RECORD_DIRECTORY) {
  156.          (*Depth)++;
  157.          if (!ReadDirectory(BuildName(Record,BFName),RList,Record,&Sub,*Depth))
  158.             return(FALSE);
  159.          Record->Sub=Sub;
  160.          if (!_ReadFloppy(RList,Sub,Depth))
  161.             return(FALSE);
  162.       }
  163.       Record=Record->Next;
  164.    }
  165.    (*Depth)--;
  166.    return(TRUE);
  167. }
  168.  
  169. void FreeAllFloppies(struct List *FList)
  170. {
  171.    while (FList->lh_Head->ln_Succ)
  172.       FreeFloppy((FLOPPY *)FList->lh_Head,TRUE);
  173. }
  174.  
  175. void FreeFloppy(FLOPPY *Floppy,BOOL remove)
  176. {
  177.    struct List *RList;
  178.  
  179.    RList=&(Floppy->Records);
  180.    while (RList->lh_Head->ln_Succ)
  181.       FreeRecord((RECORD *)RList->lh_Head,TRUE);
  182.    if (remove) Remove((struct Node *)Floppy);
  183.    FreeMem(Floppy,sizeof(FLOPPY));
  184. }
  185.  
  186. void FreeRecord(RECORD *Record,BOOL remove)
  187. {
  188.    if (Record->FName)
  189.       FreeMem(Record->FName,strlen(Record->FName)+1);
  190.    if (Record->FRem)
  191.       FreeMem(Record->FRem,strlen(Record->FRem)+1);
  192.    if (remove) Remove((struct Node *)Record);
  193.    FreeMem(Record,sizeof(RECORD));
  194. }
  195.  
  196. void DeleteBelow(RECORD *Record,BOOL DeleteHead)
  197. {
  198.    _DeleteBelow(Record->Sub);
  199.    if (DeleteHead)
  200.       DeleteRecord(Record);
  201. }
  202.  
  203. static void _DeleteBelow(RECORD *Record)
  204. {
  205.    RECORD *Rec;
  206.  
  207.    while (Record) {
  208.       _DeleteBelow(Record->Sub);
  209.       Rec=Record->Next;
  210.       DeleteRecord(Record);
  211.       Record=Rec;
  212.    }
  213. }
  214.  
  215. void DeleteRecord(RECORD *Record)
  216. {
  217.    RECORD *PrevR,*NextR;
  218.  
  219.    NextR=Record->Next;
  220.    PrevR=Record->Parent->Sub;
  221.    if (PrevR==Record)
  222.       Record->Parent->Sub=NextR;
  223.    else {
  224.       while (PrevR->Next!=Record)
  225.          PrevR=PrevR->Next;
  226.       PrevR->Next=NextR;
  227.    }
  228.    FreeRecord(Record,TRUE);
  229. }
  230.  
  231. FLOPPY *DupFloppy(FLOPPY *Floppy)
  232. {
  233.    FLOPPY *Dup;
  234.    RECORD *Rec;
  235.  
  236.    Dup=AllocMem(sizeof(FLOPPY),MEMF_CLEAR);
  237.    if (!Dup) return((FLOPPY *)-1);
  238.    NewList(&Dup->Records);
  239.    Rec=_DupFloppy(&Dup->Records,Floppy->HeadRecord,NULL);
  240.    Dup->HeadRecord=Rec;
  241.    return(Dup);
  242. }
  243.  
  244. static RECORD *_DupFloppy(struct List *RList,RECORD *Src,RECORD *Parent)
  245. {
  246.    RECORD *TopRecord = NULL;
  247.    RECORD *Record,*Sub,*Rec;
  248.  
  249.    while (Src) {
  250.       Record=DupRecord(Src);
  251.       if (TopRecord) {
  252.          for (Rec=TopRecord; Rec->Next; Rec=Rec->Next);
  253.          Rec->Next=Record;
  254.       } else
  255.          TopRecord=Record;
  256.       Record->Parent=Parent;
  257.       Record->Next=NULL;
  258.       Record->Sub=NULL;
  259.       AddTail(RList,(struct Node *)Record);
  260.       if (Src->Sub) {
  261.          Sub=_DupFloppy(RList,Src->Sub,Record);
  262.          Record->Sub=Sub;
  263.       }
  264.       Src=Src->Next;
  265.    }
  266.    return(TopRecord);
  267. }
  268.  
  269. RECORD *DupRecord(RECORD *Src)
  270. {
  271.    RECORD *Record;
  272.  
  273.    Record=AllocMem(sizeof(RECORD),MEMF_CLEAR);
  274.    *Record=*Src;
  275.    if (Src->FName) {
  276.       Record->FName=AllocMem(strlen((char *)Src->FName)+1,MEMF_CLEAR);
  277.       strcpy((char *)Record->FName,(char *)Src->FName);
  278.    }
  279.    if (Src->FRem) {
  280.       Record->FRem=AllocMem(strlen((char *)Src->FRem)+1,MEMF_CLEAR);
  281.       strcpy((char *)Record->FRem,(char *)Src->FRem);
  282.    }
  283.    return(Record);
  284. }
  285.  
  286. BOOL FindMatch(struct List *SList,STRPTR Pattern,BOOL NoCase,
  287.                BOOL DoDirs,LONGBITS KeyMask,BOOL KeyAnd)
  288. {
  289.    FLOPPY *SFloppy;
  290.    RECORD *SRecord;
  291.    char    token[132];
  292.    BOOL    NameMatch,Success;
  293.    BOOL    Found = FALSE;
  294.  
  295.    if (NoCase)
  296.       ParsePatternNoCase(Pattern,(STRPTR)token,sizeof(token)-1);
  297.    else
  298.       ParsePattern(Pattern,(STRPTR)token,sizeof(token)-1);
  299.    SFloppy=(FLOPPY *)SList->lh_Head;
  300.    while (((struct Node *)SFloppy)->ln_Succ) {
  301.       SRecord=(RECORD *)SFloppy->Records.lh_Head;
  302.       while (((struct Node *)SRecord)->ln_Succ) {
  303.          if ((!(SRecord->Flags & RECORD_DIRECTORY)) || (DoDirs)) {
  304.             if (NoCase)
  305.                NameMatch=MatchPatternNoCase((STRPTR)token,(STRPTR)SRecord->FName);
  306.             else
  307.                NameMatch=MatchPattern((STRPTR)token,(STRPTR)SRecord->FName);
  308.             if (NameMatch) {
  309.                if (!KeyMask)
  310.                   Success=TRUE;
  311.                else
  312.                   if (KeyAnd)
  313.                      Success=((KeyMask & SRecord->Keys)==KeyMask);
  314.                   else
  315.                      Success=((KeyMask & SRecord->Keys)!=NULL);
  316.                if (Success) {
  317.                   Found=TRUE;
  318.                   AddMatchToList(SRecord);
  319.                }
  320.             }
  321.          }
  322.          SRecord=(RECORD *)(((struct Node *)SRecord)->ln_Succ);
  323.       }
  324.       SFloppy=(FLOPPY *)(((struct Node *)SFloppy)->ln_Succ);
  325.    }
  326.    return(Found);
  327. }
  328.  
  329. void AddFloppyInPlace(struct List *fList,struct Node *fNode)
  330. {
  331.    RECORD      *Record;
  332.    struct Node *Node;
  333.    STRPTR       String;
  334.  
  335.    Record=((FLOPPY *)fNode)->HeadRecord;
  336.    if (!Record) {
  337.       AddHead(fList,fNode);
  338.       return;
  339.    }
  340.    String=Record->FName;
  341.    Node=fList->lh_Head;
  342.    while (Node->ln_Succ) {
  343.       Record=((FLOPPY *)Node)->HeadRecord;
  344.       if (Record) {
  345.          if (stricmp((char *)String,(char *)Record->FName)<0) {
  346.             Insert(fList,fNode,Node->ln_Pred);
  347.             return;
  348.          }
  349.       }
  350.       Node=Node->ln_Succ;
  351.    }
  352.    AddTail(fList,fNode);
  353. }
  354.  
  355. BOOL AddRecordInPlace(struct List *rList,struct Node *rNode,struct Node *pNode)
  356. {
  357.    RECORD      *Record;
  358.    struct Node *Node;
  359.    STRPTR       String;
  360.  
  361.    String=((RECORD *)rNode)->FName;
  362.    Node=pNode->ln_Succ;
  363.    while (Node->ln_Succ) {
  364.       Record=(RECORD *)Node;
  365.       if (Record->Parent!=(RECORD *)pNode) break;
  366.       if (stricmp((char *)String,(char *)Record->FName)<0) {
  367.          Insert(rList,rNode,Node->ln_Pred);
  368.          ((RECORD *)rNode)->Next=(RECORD *)Node;
  369.          if (rNode->ln_Pred!=pNode) {
  370.             ((RECORD *)rNode->ln_Pred)->Next=(RECORD *)rNode;
  371.             return(FALSE);
  372.          } else
  373.             return(TRUE);
  374.       }
  375.       Node=Node->ln_Succ;
  376.    }
  377.    Insert(rList,rNode,Node->ln_Pred);
  378.    ((RECORD *)rNode)->Next=NULL;
  379.    if (rNode->ln_Pred!=pNode) {
  380.       ((RECORD *)rNode->ln_Pred)->Next=(RECORD *)rNode;
  381.       return(FALSE);
  382.    } else
  383.       return(TRUE);
  384. }
  385.  
  386. void ResetKeys()
  387. {
  388.    int i;
  389.  
  390.    for (i=0; i<MAXKEYS; i++)
  391.       KeyList[i]=NULL;
  392. }
  393.  
  394. void FreeKeys()
  395. {
  396.    int i;
  397.  
  398.    ClearKeyLView();
  399.    for (i=0; i<MAXKEYS; i++)
  400.       if (KeyList[i]) {
  401.          FreeMem(KeyList[i],strlen(KeyList[i])+1);
  402.          KeyList[i]=NULL;
  403.       }
  404. }
  405.  
  406. void CopyFromKeys()
  407. {
  408.    int i;
  409.  
  410.    for (i=0; i<MAXKEYS; i++)
  411.       if (KeyList[i]) {
  412.          KeyListCopy[i]=AllocMem(strlen(KeyList[i])+1,MEMF_CLEAR);
  413.          strcpy(KeyListCopy[i],KeyList[i]);
  414.       } else
  415.          KeyListCopy[i]=NULL;
  416. }
  417.  
  418. void CopyToKeys()
  419. {
  420.    int i;
  421.  
  422.    FreeKeys();
  423.    for (i=0; i<MAXKEYS; i++)
  424.       if (KeyListCopy[i]) {
  425.          KeyList[i]=AllocMem(strlen(KeyListCopy[i])+1,MEMF_CLEAR);
  426.          strcpy(KeyList[i],KeyListCopy[i]);
  427.       }
  428. }
  429.  
  430. void TestKeyDelete()
  431. {
  432.    int i;
  433.  
  434.    for (i=0; i<MAXKEYS; i++)
  435.       if ((!KeyList[i]) && (KeyListCopy[i]))
  436.             RemoveKeyFromFloppies(&FloppyList,~(1<<i));
  437. }
  438.  
  439. void FreeKeyCopy()
  440. {
  441.    int i;
  442.  
  443.    for (i=0; i<MAXKEYS; i++)
  444.       if (KeyListCopy[i]) {
  445.          FreeMem(KeyListCopy[i],strlen(KeyListCopy[i])+1);
  446.          KeyListCopy[i]=NULL;
  447.       }
  448. }
  449.  
  450. STRPTR *AddKeyToList(STRPTR KName,BOOL *Full)
  451. {
  452.    int i,j;
  453.  
  454.    for (i=0; i<MAXKEYS; i++)
  455.       if (KeyList[i]==NULL) {
  456.          KeyList[i]=AllocMem(strlen(KName)+1,MEMF_CLEAR);
  457.          strcpy(KeyList[i],KName);
  458.          for (j=i+1,*Full=TRUE; j<MAXKEYS; j++)
  459.             if (KeyList[j]==NULL)
  460.                *Full=FALSE;
  461.          return(&KeyList[i]);
  462.       }
  463.    return(NULL);
  464. }
  465.  
  466. STRPTR *ChangeKeyList(STRPTR OldKey,STRPTR KName)
  467. {
  468.    int i;
  469.  
  470.    for (i=0; i<MAXKEYS; i++)
  471.       if (KeyList[i]==OldKey) {
  472.          FreeMem(OldKey,strlen(OldKey)+1);
  473.          KeyList[i]=AllocMem(strlen(KName)+1,MEMF_CLEAR);
  474.          strcpy(KeyList[i],KName);
  475.          return(&KeyList[i]);
  476.       }
  477.    return(NULL);
  478. }
  479.  
  480. void DelKeyFromList(STRPTR KName)
  481. {
  482.    int i;
  483.  
  484.    for (i=0; i<MAXKEYS; i++)
  485.       if (KeyList[i]==KName) {
  486.          FreeMem(KName,strlen(KName)+1);
  487.          KeyList[i]=NULL;
  488.          return;
  489.       }
  490. }
  491.  
  492. void InitKeyScan()
  493. {
  494.    KeyScan=0;
  495. }
  496.  
  497. STRPTR *GetNextKey(WORD *KeyNum)
  498. {
  499.    while (KeyScan<MAXKEYS && KeyList[KeyScan]==NULL)
  500.       KeyScan++;
  501.    *KeyNum=KeyScan;
  502.    if (KeyScan==MAXKEYS)
  503.       return(NULL);
  504.    else
  505.       return(&KeyList[KeyScan++]);
  506. }
  507.  
  508. WORD KeyNumber(STRPTR Key)
  509. {
  510.    WORD i;
  511.  
  512.    for (i=0; i<MAXKEYS; i++)
  513.       if (KeyList[i]==Key) {
  514.          return(i);
  515.       }
  516.    return(-1);
  517. }
  518.  
  519. STRPTR *NumberKey(WORD Num)
  520. {
  521.    return(&KeyList[Num]);
  522. }
  523.  
  524. void AddKeyInPos(WORD KeyNum,STRPTR Key)
  525. {
  526.    KeyList[KeyNum]=AllocMem(strlen(Key)+1,MEMF_CLEAR);
  527.    strcpy(KeyList[KeyNum],Key);
  528.    AddKeyToLView(&KeyList[KeyNum]);
  529. }
  530.  
  531. void RemoveKeyFromFloppies(struct List *FList,LONGBITS KeyMask)
  532. {
  533.    FLOPPY *Floppy;
  534.    RECORD *Record;
  535.  
  536.    Floppy=(FLOPPY *)FList->lh_Head;
  537.    while (((struct Node *)Floppy)->ln_Succ) {
  538.       Record=(RECORD *)Floppy->Records.lh_Head;
  539.       while (((struct Node *)Record)->ln_Succ) {
  540.          Record->Keys&=KeyMask;
  541.          Record=(RECORD *)(((struct Node *)Record)->ln_Succ);
  542.       }
  543.       Floppy=(FLOPPY *)(((struct Node *)Floppy)->ln_Succ);
  544.    }
  545. }
  546.  
  547. void KeysBelow(RECORD *Record,LONGBITS AddMask,LONGBITS RemMask)
  548. {
  549.    while (Record) {
  550.       KeysBelow(Record->Sub,AddMask,RemMask);
  551.       Record->Keys|=AddMask;
  552.       Record->Keys&=RemMask;
  553.       Record=Record->Next;
  554.    }
  555. }
  556.  
  557. void SalvageData(FLOPPY *DstF,FLOPPY *SrcF,LONG Type)
  558. {
  559.    RECORD *SrcR,*DstR;
  560.    RECORD *SrcR2;
  561.    char    SrcN[108],DstN[108];
  562.    BOOL    Found;
  563.  
  564.    DstR=(RECORD *)DstF->Records.lh_Head;
  565.    while (((struct Node *)DstR)->ln_Succ) {
  566.       BuildName(DstR,DstN);
  567.       Found=FALSE;
  568.       SrcR=(RECORD *)SrcF->Records.lh_Head;
  569.       SrcR2=NULL;
  570.       while ((!Found) && (((struct Node *)SrcR)->ln_Succ)) {
  571.          BuildName(SrcR,SrcN);
  572.          if (strcmp(DstN,SrcN)==0) {
  573.             Found=TRUE;
  574.             break;
  575.          }
  576.          if (Type>1)
  577.             if (strcmp(DstR->FName,SrcR->FName)==0)
  578.                SrcR2=SrcR;
  579.          SrcR=(RECORD *)(((struct Node *)SrcR)->ln_Succ);
  580.       }
  581.       if ((!Found) && (SrcR2)) {
  582.          SrcR=SrcR2;
  583.          Found=TRUE;
  584.       }
  585.       if (Found) {
  586.          if (SrcR->FRem) {
  587.             if (DstR->FRem)
  588.                FreeMem(DstR->FRem,strlen(DstR->FRem)+1);
  589.             DstR->FRem=AllocMem(strlen(SrcR->FRem)+1,MEMF_CLEAR);
  590.             strcpy(DstR->FRem,SrcR->FRem);
  591.          }
  592.          DstR->Keys=SrcR->Keys;
  593.       }
  594.       DstR=(RECORD *)(((struct Node *)DstR)->ln_Succ);
  595.    }
  596. }
  597.